package com.haowang.camera.module;

import com.haowang.camera.activity.CameraActivity;
import com.haowang.camera.manager.CameraManager;
import com.haowang.camera.manager.CameraManagerBase;
import com.haowang.camera.manager.GestureManager;
import com.haowang.camera.manager.PreviewManager;
import com.haowang.camera.manager.SurfaceHorderPreviewManager;
import com.haowang.camera.manager.SurfaceTexturePreviewManager;
import com.haowang.camera.util.ApiHelper;
import com.haowang.camera.util.GlobalValues;

import android.content.res.Configuration;
import android.hardware.Camera;
import android.hardware.Camera.Parameters;
import android.os.Handler;
import android.os.Message;
import android.util.Log;
import android.widget.ImageButton;

/**
 * Created by wh on 2/4/14.
 */
public abstract class CameraModule {

	private static final String TAG = CameraModule.class.getSimpleName();

	private CameraStartUpThread mCameraStartUpThread;
	private final Handler mHandler = new MainHandler();

	protected static final int CAMERA_OPEN_DONE = 9;
	protected static final int START_PREVIEW_DONE = 10;
	protected static final int OPEN_CAMERA_FAIL = 11;
	protected static final int CAMERA_START_THREAD_COMPLETED = 12;

	protected int mCameraId = GlobalValues.BACK_CAMERA;
	protected CameraActivity mActivity;
	protected Camera mCameraDevice;
	protected Parameters mParameters;
	protected PreviewManager mPreviewManager;
	protected GestureManager mGestureManager;

	protected ImageButton mShutterButton;

	public CameraModule(CameraActivity context) {
		mActivity = context;
	}

	public Camera getCameraDevice() {
		return mCameraDevice;
	}

	public GestureManager getGestureManager() {
		return mGestureManager;
	}

	public CameraStartUpThread getCameraStartUpThread() {
		return mCameraStartUpThread;
	}

	public void init() {
		mGestureManager = new GestureManager(mActivity);
		mGestureManager.init();
	}

	public void onCreate() {
		Log.i(TAG, "onCreate");
		mCameraStartUpThread = new CameraStartUpThread();
		mCameraStartUpThread.start();
	}

	public void onResume() {
		Log.i(TAG, "onResume");
		if (mCameraStartUpThread == null
				&& CameraManager.instance().getCameraState() == CameraManager.CAMERA_CLOSED) {
			mCameraStartUpThread = new CameraStartUpThread();
			mCameraStartUpThread.start();
		}
	}

	public void onBackPressed() {
		Log.i(TAG, "onBackPressed");
	}

	public void onPause() {
		Log.i(TAG, "onPause");
		try {
			mCameraStartUpThread.join();
		} catch (Exception e) {
		}
		mCameraStartUpThread = null;
		releaseCamera();
	}

	public void onDestroy() {
		Log.i(TAG, "onDestroy");
		CameraManagerBase.resetAllManagers();
	}

	protected void releaseCamera() {
		CameraManager.instance().releaseCamera();
	}

	public void onFullScreenChanged(boolean full) {
	}

	public void onConfigurationChanged(Configuration config) {
	}

	public void startPreview(boolean forceStop) throws Exception {
	}

	public void stopPreview() throws Exception {
		CameraManager.instance().stopPreview();
	}

	public void initParameters() {
	}

	// The purpose is not to block the main thread in onCreate and onResume.
	private class CameraStartUpThread extends Thread {
		@Override
		public void run() {
			try {
				mCameraDevice = CameraManager.instance().getCameraDevice(
						mCameraId);
				mHandler.sendEmptyMessage(CAMERA_OPEN_DONE);

				initParameters();

				startPreview(false);
				mHandler.sendEmptyMessage(START_PREVIEW_DONE);
			} catch (Exception e) {
				Log.e(TAG,
						"Camera startup Thread occur a error!:"
								+ e.getMessage());
				mHandler.sendEmptyMessage(OPEN_CAMERA_FAIL);
			}

			mHandler.sendEmptyMessage(CAMERA_START_THREAD_COMPLETED);
		}
	}

	private class MainHandler extends Handler {
		@Override
		public void handleMessage(Message msg) {
			switch (msg.what) {

			case CAMERA_OPEN_DONE:
				cameraOpenDone();
				break;

			case START_PREVIEW_DONE:
				startPreviewDone();
				break;

			case OPEN_CAMERA_FAIL:
				openCameraFailed();
				break;

			case CAMERA_START_THREAD_COMPLETED:
				mCameraStartUpThread = null;
				break;

			}
		}

		private void cameraOpenDone() {
			// TODO Auto-generated method stub

		}

		private void startPreviewDone() {
			// TODO Auto-generated method stub

		}

		private void openCameraFailed() {
			// TODO Auto-generated method stub

		}
	}
}
